/**
 @file ctc_srv6.h

 @author  Copyright (C) 2014 Centec Networks Inc.  All rights reserved.

 @date 2019-1-1

 @version v6.0

 Segment Routing provides complete control over the forwarding paths by combining simple network instructions.
 It does not require any additional protocol. Indeed in some cases it removes unnecessary protocols simplifying your network.
 \b
 Segment Routing can be used to steer traffic along any arbitrary path in the network. This allows operators to
 enforce low-latency and / or disjoint paths, regardless of the normal forwarding paths
 \b
 The IPv6 flavor of Segment Routing allows user-defined functions to be associated with segments. By leveraging
 the IPv6 SID format and the dedicated Segment Routing Extension Header, these functions may implement any computable
 behavior allowing for Network Function Virtualization
 \b

\b
\p
The module provides APIs to support SRv6:
\p
\d Add SID table by ctcs_srv6_add_my_sid()
\d Remove SID by ctcs_srv6_remove_my_sid()
\d Update SID action by ctcs_srv6_update_my_sid()

\S ctc_srv6.h:ctc_srv6_type_t
\S ctc_srv6.h:ctc_srv6_sid_flag_t
\S ctc_srv6.h:ctc_srv6_sid_t

*/

#ifndef _CTC_SRV6_H
#define _CTC_SRV6_H
#ifdef __cplusplus
extern "C" {
#endif
/****************************************************************
 *
 * Header Files
 *
 ***************************************************************/
#include "ctc_const.h"
#include "ctc_common.h"

/****************************************************************
*
* Defines and Macros
*
****************************************************************/
/**
 @brief  Functions associated with a SID
*/
enum ctc_srv6_type_e
{
    CTC_SRV6_TYPE_NONE,         /**< [TMM.AT] Endpoint without specific behavior */
    CTC_SRV6_TYPE_E,            /**< [TMM.AT] Endpoint */
    CTC_SRV6_TYPE_X,            /**< [TMM.AT] Endpoint with cross-connect to an array of layer-3 adjacencies */
    CTC_SRV6_TYPE_T,            /**< [TMM.AT] Endpoint with specific IPv6 table lookup */
    CTC_SRV6_TYPE_DX2,          /**< [TMM.AT] Endpoint with decapsulation and Layer-2 cross-connect to OIF */
    CTC_SRV6_TYPE_DT2U,         /**< [TMM.AT] Endpoint with decapsulation and specific unicast MAC L2 table lookup */
    CTC_SRV6_TYPE_DT2M,         /**< [TMM.AT] Endpoint with decapsulation and specific L2 table flooding */
    CTC_SRV6_TYPE_DX6,          /**< [TMM.AT] Endpoint with decapsulation and cross-connect to an array of IPv6 adjacencies */
    CTC_SRV6_TYPE_DX4,          /**< [TMM.AT] Endpoint with decapsulation and cross-connect to an array of IPv4 adjacencies */
    CTC_SRV6_TYPE_DT6,          /**< [TMM.AT] Endpoint with decapsulation and specific IPv6 table lookup */
    CTC_SRV6_TYPE_DT4,          /**< [TMM.AT] Endpoint with decapsulation and specific IPv4 table lookup */
    CTC_SRV6_TYPE_DT46,         /**< [TMM.AT] Endpoint with decapsulation and specific IP table lookup */
    CTC_SRV6_TYPE_INSERT,       /**< [TMM.AT] Endpoint bound to an SRv6 Policy */
    CTC_SRV6_TYPE_ENCAPS,       /**< [TMM.AT] Endpoint bound to an SRv6 policy with encaps */
    CTC_SRV6_TYPE_AM,           /**< [TMM.AT] Endpoint used as masquerading proxy */
    CTC_SRV6_TYPE_DT,           /**< [TMM.AT] Endpoint with decapsulation and specific MAC or IP lookup*/
    CTC_SRV6_TYPE_MAX
};
typedef enum ctc_srv6_type_e ctc_srv6_type_t;

/**
 @brief  Edit Type associated with a SID
*/
enum ctc_srv6_edit_type_e
{
    CTC_SRV6_EDIT_TYPE_0  = 1,  /**< [TMM.AT] Normal SID:Decrement SL by 1;Update IPv6 DA with Segment List[SL]
                                      Normal SID+PSP:Update IPv6 DA with Segment List[SL-1];Remove the SRH from the IPv6 extension header chain
                                      uSID:Copy IPv6 DA [X..127] into IPv6 DA [(X-16)..111] and set IPv6 DA [112..127] to 0x0000
                                      gSID+COC:Decrement SI by 1;Update current gSID with Segment List[Segments Left][SI]
                                      gSID:Decrement SL by 1;Update IPv6 DA with Segment List[SL];Set SI to 3 */
    CTC_SRV6_EDIT_TYPE_1  = 2,  /**< [TMM.AT] Normal SID:Decrement Segments Left by 1;Update IPv6 DA with Segment List[0] */
    CTC_SRV6_EDIT_TYPE_2  = 3,  /**< [TMM.AT] Normal SID:Update IPv6 DA with Segment List[Segments Left] */
    CTC_SRV6_EDIT_TYPE_MAX
};
typedef enum ctc_srv6_edit_type_e ctc_srv6_edit_type_t;

/**
 @brief enum value used in my sid flag APIs
*/
enum ctc_srv6_sid_flag_e
{
    CTC_SRV6_SID_FLAG_LOGIC_PORT_TYPE           = 0x0001, /**< [TMM.AT] If set, means do horizon split */
    CTC_SRV6_SID_FLAG_DENY_LEARNING             = 0x0002, /**< [TMM.AT] Deny inner learning */
    CTC_SRV6_SID_FLAG_ACL_LKUP_BY_OUTER_HEAD    = 0x0004, /**< [TMM.AT] Use outer header info do acl flow lookup */
    CTC_SRV6_SID_FLAG_PSP_EN                    = 0x0008, /**< [TMM.AT] Enable PSP */
    CTC_SRV6_SID_FLAG_TTL_CHECK                 = 0x0010, /**< [TMM.AT] Do ttl check if set */
    CTC_SRV6_SID_FLAG_USE_OUTER_TTL             = 0x0020, /**< [TMM.AT] Route will use outer header TTL */
    CTC_SRV6_SID_FLAG_USE_FLEX                  = 0x0040, /**< [TMM.AT] Means use tcam */
    CTC_SRV6_SID_FLAG_COPY_TO_CPU               = 0x0080, /**< [TMM.AT] Indicate packet will copy to CPU */
    CTC_SRV6_SID_FLAG_DISCARD                   = 0x0100, /**< [TMM.AT] Indicate packet will discard */
    CTC_SRV6_SID_FLAG_COC_EN                    = 0x0200, /**< [TMM.AT] Enable COC for gsid */
    CTC_SRV6_SID_FLAG_LEGALITY_CHECK_DIS        = 0x0400, /**< [TMM.AT] Disable SRH fields check. Default is enable */
    CTC_SRV6_SID_FLAG_DECAP_EN                  = 0x0800, /**< [TMM.AT] Enable decap. Valid when srv6 type is CTC_SRV6_TYPE_NONE */
    CTC_SRV6_SID_FLAG_USD_EN                    = 0x1000, /**< [AT] Enable USD */
    CTC_SRV6_SID_FLAG_USP_EN                    = 0x2000, /**< [AT] Enable USP */
    CTC_SRV6_SID_FLAG_DE_MASQ                   = 0x4000  /**< [AT] Enable de-masquerading of srv6 type END.AM */
};
typedef enum ctc_srv6_sid_flag_e ctc_srv6_sid_flag_t;

/**
 @brief  Define My SID Format
*/
enum ctc_srv6_sid_format_e
{
  CTC_SRV6_SID_FORMAT_NORMAL          = 0x1,  /**< [TMM.AT] Normal Segment Identifier */
  CTC_SRV6_SID_FORMAT_USID            = 0x2,  /**< [TMM.AT] Micro Segment Identifier */
  CTC_SRV6_SID_FORMAT_GSID            = 0x4,  /**< [TMM.AT] Generalized Segment Identifier */
  CTC_SRV6_SID_FORMAT_MAX
};
typedef enum ctc_srv6_sid_format_e ctc_srv6_sid_format_t;

/**
 @brief  Define My SID Structure
*/
struct ctc_srv6_sid_s
{
    ipv6_addr_t sid;                         /**< [TMM.AT] Segment Identifier */
    uint8  masklen;                          /**< [TMM.AT] Mask length of sid, only for tcam */

    ctc_srv6_type_t type;                    /**< [TMM.AT] Behavior type associated with a SID. Refer to ctc_srv6_type_t */
    ctc_srv6_edit_type_t edit_type;          /**< [TMM.AT] Srv6 packet edit type associated with a SID.
                                                        Valid when srv6 type is CTC_SRV6_TYPE_NONE.
                                                        Refer to ctc_srv6_edit_type_t */
    ctc_srv6_sid_format_t format;            /**< [TMM.AT] Choose SID format. Refer to ctc_srv6_sid_format_t*/
    uint8 scl_id;                            /**< [TMM.AT] SCL lookup ID */
    uint32 flag;                             /**< [TMM.AT] Refer to ctc_srv6_sid_flag_t */
    uint32 nh_id;                            /**< [TMM.AT] Nexthop id, need create nexthop first */
    uint16 fid;                              /**< [TMM.AT] Forwarding instance, maybe EVC concept on MEF10. 0 means disable */
    uint16 vrf_id;                           /**< [TMM.AT] Vrf ID of the route. 0 means disable */
    uint16 logic_port;                       /**< [TMM.AT] Logic source port */
    uint32 stats_id;                         /**< [TMM.AT] Stats id */
    uint16 policer_id;                       /**< [TMM.AT] Policer id for service policer */
	mac_addr_t route_mac;                    /**< [TMM.AT] Route mac for inner packet, 0.0.0 means disable. */
    uint32 scl_entry_id;                     /**< [TMM.AT] [out]Scl entry id. Add more action for SID. Refer to ctcs_tmx_scl_add_action_field*/
    uint8 inner_pkt_type;                    /**< [TMM.AT] Inner packet type, refer to packet_type_t. Valid when srv6 type is CTC_SRV6_TYPE_NONE */

    uint16 pp_bmp;                            /**< [AT] Pipeline bitmap */
};
typedef struct ctc_srv6_sid_s ctc_srv6_sid_t;

/**
 @brief  Global config associated with SID
*/
struct ctc_srv6_global_cfg_s
{
    uint8 sid_format_bmp;            /**< [TMM.AT] Choose Segment Identifier Format bitmap. Refer to ctc_srv6_sid_format_t.(default: 1)*/
};
typedef struct ctc_srv6_global_cfg_s ctc_srv6_global_cfg_t;


#ifdef __cplusplus
}
#endif

#endif

